কেরাসের সাথে পালিগেমা আউটপুট তৈরি করুন

ai.google.dev-এ দেখুন Google Colab-এ চালান GitHub-এ উৎস দেখুন

PaliGemma মডেলগুলির মাল্টিমোডাল ক্ষমতা রয়েছে, যা আপনাকে পাঠ্য এবং চিত্র ইনপুট ডেটা উভয় ব্যবহার করে আউটপুট তৈরি করতে দেয়। আপনি আপনার অনুরোধের জন্য অতিরিক্ত প্রসঙ্গ প্রদান করতে এই মডেলগুলির সাথে ইমেজ ডেটা ব্যবহার করতে পারেন, বা ছবির বিষয়বস্তু বিশ্লেষণ করতে মডেলটি ব্যবহার করতে পারেন। এই টিউটোরিয়ালটি আপনাকে দেখায় কিভাবে কেরাসের সাথে PaliGemma ব্যবহার করে ছবিগুলি বিশ্লেষণ করতে এবং সেগুলি সম্পর্কে প্রশ্নের উত্তর দিতে পারেন৷

কি আছে এই নোটবুকে

এই নোটবুকটি কেরাসের সাথে পালিগেমা ব্যবহার করে এবং আপনাকে দেখায় কিভাবে:

  • Keras এবং প্রয়োজনীয় নির্ভরতা ইনস্টল করুন
  • PaliGemmaCausalLM ডাউনলোড করুন, কার্যকারণ ভিজ্যুয়াল ল্যাঙ্গুয়েজ মডেলিংয়ের জন্য একটি প্রাক-প্রশিক্ষিত PaliGemma ভেরিয়েন্ট, এবং একটি মডেল তৈরি করতে এটি ব্যবহার করুন
  • সরবরাহকৃত ছবি সম্পর্কে তথ্য অনুমান করার মডেলের ক্ষমতা পরীক্ষা করুন

আপনি শুরু করার আগে

এই নোটবুকের মধ্য দিয়ে যাওয়ার আগে, আপনাকে পাইথন কোডের সাথে পরিচিত হওয়া উচিত, সেইসাথে কীভাবে বড় ভাষা মডেল (LLM) প্রশিক্ষিত হয়। আপনার কেরাসের সাথে পরিচিত হওয়ার দরকার নেই, তবে উদাহরণ কোডটি পড়ার সময় কেরাস সম্পর্কে প্রাথমিক জ্ঞান সহায়ক।

সেটআপ

নিম্নলিখিত বিভাগগুলি একটি PaliGemma মডেল ব্যবহার করার জন্য একটি নোটবুক পাওয়ার প্রাথমিক পদক্ষেপগুলি ব্যাখ্যা করে, যার মধ্যে মডেল অ্যাক্সেস, একটি API কী পাওয়া এবং নোটবুকের রানটাইম কনফিগার করা রয়েছে৷

PaliGemma অ্যাক্সেস পান

প্রথমবারের জন্য PaliGemma ব্যবহার করার আগে, আপনাকে অবশ্যই নিম্নলিখিত ধাপগুলি সম্পূর্ণ করে কাগলের মাধ্যমে মডেলটিতে অ্যাক্সেসের অনুরোধ করতে হবে:

  1. Kaggle এ লগ ইন করুন, অথবা আপনার যদি ইতিমধ্যে একটি না থাকে তাহলে একটি নতুন Kaggle অ্যাকাউন্ট তৈরি করুন৷
  2. PaliGemma মডেল কার্ডে যান এবং অ্যাক্সেসের অনুরোধ করুন ক্লিক করুন।
  3. সম্মতি ফর্মটি পূরণ করুন এবং শর্তাবলী গ্রহণ করুন।

আপনার API কী কনফিগার করুন

PaliGemma ব্যবহার করতে, আপনাকে অবশ্যই আপনার Kaggle ব্যবহারকারীর নাম এবং একটি Kaggle API কী প্রদান করতে হবে।

একটি Kaggle API কী তৈরি করতে, Kaggle-এ আপনার সেটিংস পৃষ্ঠা খুলুন এবং নতুন টোকেন তৈরি করুন ক্লিক করুন। এটি আপনার API শংসাপত্র ধারণকারী একটি kaggle.json ফাইলের ডাউনলোডকে ট্রিগার করে।

তারপর, Colab-এ, বাম ফলকে সিক্রেটস (🔑) নির্বাচন করুন এবং আপনার Kaggle ব্যবহারকারীর নাম এবং Kaggle API কী যোগ করুন। KAGGLE_USERNAME নামে আপনার ব্যবহারকারীর নাম এবং KAGGLE_KEY নামের অধীনে আপনার API কী সংরক্ষণ করুন।

রানটাইম নির্বাচন করুন

এই টিউটোরিয়ালটি সম্পূর্ণ করার জন্য, আপনার PaliGemma মডেল চালানোর জন্য পর্যাপ্ত সম্পদ সহ একটি Colab রানটাইম থাকতে হবে। এই ক্ষেত্রে, আপনি একটি T4 GPU ব্যবহার করতে পারেন:

  1. Colab উইন্ডোর উপরের ডানদিকে, ▾ (অতিরিক্ত সংযোগ বিকল্প) ড্রপডাউন মেনুতে ক্লিক করুন।
  2. রানটাইম পরিবর্তন নির্বাচন করুন।
  3. হার্ডওয়্যার এক্সিলারেটরের অধীনে, T4 GPU নির্বাচন করুন।

পরিবেশের ভেরিয়েবল সেট করুন

KAGGLE_USERNAME , KAGGLE_KEY , এবং KERAS_BACKEND এর জন্য পরিবেশ ভেরিয়েবল সেট করুন।

import os
from google.colab import userdata

# Set up environmental variables
os.environ["KAGGLE_USERNAME"] = userdata.get('KAGGLE_USERNAME')
os.environ["KAGGLE_KEY"] = userdata.get('KAGGLE_KEY')
os.environ["KERAS_BACKEND"] = "jax"

কেরাস ইনস্টল করুন

কেরাস ইনস্টল করতে নীচের সেলটি চালান।

pip install -U -q keras-nlp keras-hub kagglehub

নির্ভরতা আমদানি করুন এবং কেরাস কনফিগার করুন

এই নোটবুকের জন্য প্রয়োজনীয় নির্ভরতা ইনস্টল করুন এবং কেরাসের ব্যাকএন্ড কনফিগার করুন। আপনি কেরাসকে bfloat16 ব্যবহার করতে সেট করবেন যাতে ফ্রেমওয়ার্ক কম মেমরি ব্যবহার করে।

import keras
import keras_hub
import numpy as np
import PIL
import requests
import io
import matplotlib
import re
import matplotlib.pyplot as plt
import matplotlib.patches as patches
from PIL import Image

keras.config.set_floatx("bfloat16")

মডেল লোড করুন

এখন যেহেতু আপনি সবকিছু সেট আপ করেছেন, আপনি প্রাক-প্রশিক্ষিত মডেলটি ডাউনলোড করতে পারেন এবং আপনার মডেলটিকে এর প্রতিক্রিয়া তৈরি করতে সহায়তা করার জন্য কিছু ইউটিলিটি পদ্ধতি তৈরি করতে পারেন। এই ধাপে, আপনি কেরাস হাব থেকে PaliGemmaCausalLM ব্যবহার করে একটি মডেল ডাউনলোড করুন। এই শ্রেণীটি আপনাকে PaliGemma-এর কার্যকারণ ভিজ্যুয়াল ল্যাঙ্গুয়েজ মডেল কাঠামো পরিচালনা ও চালাতে সাহায্য করে। একটি কার্যকারণ চাক্ষুষ ভাষা মডেল পূর্ববর্তী টোকেনগুলির উপর ভিত্তি করে পরবর্তী টোকেনের পূর্বাভাস দেয়। কেরাস হাব অনেক জনপ্রিয় মডেল আর্কিটেকচারের বাস্তবায়ন প্রদান করে।

from_preset পদ্ধতি ব্যবহার করে মডেল তৈরি করুন এবং এর সারাংশ প্রিন্ট করুন। এই প্রক্রিয়াটি সম্পূর্ণ হতে প্রায় এক মিনিট সময় লাগবে।

paligemma = keras_hub.models.PaliGemmaCausalLM.from_preset("kaggle://keras/paligemma2/keras/pali_gemma2_mix_3b_224")
paligemma.summary()

ইউটিলিটি পদ্ধতি তৈরি করুন

আপনার মডেল থেকে প্রতিক্রিয়া তৈরি করতে সাহায্য করার জন্য, দুটি ইউটিলিটি পদ্ধতি তৈরি করুন:

  • crop_and_resize : read_img জন্য সহায়ক পদ্ধতি। এই পদ্ধতিটি চিত্রটিকে ক্রপ করে এবং আকারে পাস করা আকারে পুনরায় আকার দেয় যাতে চূড়ান্ত চিত্রটি চিত্রের অনুপাতকে বিচ্ছিন্ন না করেই পুনরায় আকার দেওয়া হয়।
  • read_img : read_img_from_url এর জন্য সহায়ক পদ্ধতি। এই পদ্ধতিটি আসলে ইমেজটি খোলে, এটিকে পুনরায় আকার দেয় যাতে এটি মডেলের সীমাবদ্ধতার সাথে ফিট করে এবং এটিকে একটি অ্যারেতে রাখে যা মডেল দ্বারা ব্যাখ্যা করা যেতে পারে।
  • read_img_from_url : একটি বৈধ URL এর মাধ্যমে একটি চিত্র নেয়৷ মডেলে ইমেজ পাস করার জন্য আপনার এই পদ্ধতির প্রয়োজন।

আপনি এই নোটবুকের পরবর্তী ধাপে read_img_from_url ব্যবহার করবেন।

def crop_and_resize(image, target_size):
    width, height = image.size
    source_size = min(image.size)
    left = width // 2 - source_size // 2
    top = height // 2 - source_size // 2
    right, bottom = left + source_size, top + source_size
    return image.resize(target_size, box=(left, top, right, bottom))

def read_image(url, target_size):
    contents = io.BytesIO(requests.get(url).content)
    image = PIL.Image.open(contents)
    image = crop_and_resize(image, target_size)
    image = np.array(image)
    # Remove alpha channel if necessary.
    if image.shape[2] == 4:
        image = image[:, :, :3]
    return image

def parse_bbox_and_labels(detokenized_output: str):
  matches = re.finditer(
      '<loc(?P<y0>\d\d\d\d)><loc(?P<x0>\d\d\d\d)><loc(?P<y1>\d\d\d\d)><loc(?P<x1>\d\d\d\d)>'
      ' (?P<label>.+?)( ;|$)',
      detokenized_output,
  )
  labels, boxes = [], []
  fmt = lambda x: float(x) / 1024.0
  for m in matches:
    d = m.groupdict()
    boxes.append([fmt(d['y0']), fmt(d['x0']), fmt(d['y1']), fmt(d['x1'])])
    labels.append(d['label'])
  return np.array(boxes), np.array(labels)

def display_boxes(image, boxes, labels, target_image_size):
  h, l = target_size
  fig, ax = plt.subplots()
  ax.imshow(image)
  for i in range(boxes.shape[0]):
      y, x, y2, x2 = (boxes[i]*h)
      width = x2 - x
      height = y2 - y
      # Create a Rectangle patch
      rect = patches.Rectangle((x, y),
                               width,
                               height,
                               linewidth=1,
                               edgecolor='r',
                               facecolor='none')
      # Add label
      plt.text(x, y, labels[i], color='red', fontsize=12)
      # Add the patch to the Axes
      ax.add_patch(rect)

  plt.show()

def display_segment_output(image, bounding_box, segment_mask, target_image_size):
    # Initialize a full mask with the target size
    full_mask = np.zeros(target_image_size, dtype=np.uint8)
    target_width, target_height = target_image_size

    for bbox, mask in zip(bounding_box, segment_mask):
        y1, x1, y2, x2 = bbox
        x1 = int(x1 * target_width)
        y1 = int(y1 * target_height)
        x2 = int(x2 * target_width)
        y2 = int(y2 * target_height)

        # Ensure mask is 2D before converting to Image
        if mask.ndim == 3:
            mask = mask.squeeze(axis=-1)
        mask = Image.fromarray(mask)
        mask = mask.resize((x2 - x1, y2 - y1), resample=Image.NEAREST)
        mask = np.array(mask)
        binary_mask = (mask > 0.5).astype(np.uint8)


        # Place the binary mask onto the full mask
        full_mask[y1:y2, x1:x2] = np.maximum(full_mask[y1:y2, x1:x2], binary_mask)
    cmap = plt.get_cmap('jet')
    colored_mask = cmap(full_mask / 1.0)
    colored_mask = (colored_mask[:, :, :3] * 255).astype(np.uint8)
    if isinstance(image, Image.Image):
        image = np.array(image)
    blended_image = image.copy()
    mask_indices = full_mask > 0
    alpha = 0.5

    for c in range(3):
        blended_image[:, :, c] = np.where(mask_indices,
                                          (1 - alpha) * image[:, :, c] + alpha * colored_mask[:, :, c],
                                          image[:, :, c])

    fig, ax = plt.subplots()
    ax.imshow(blended_image)
    plt.show()

আউটপুট তৈরি করুন

মডেল লোড করার পরে এবং ইউটিলিটি পদ্ধতি তৈরি করার পরে, আপনি প্রতিক্রিয়া তৈরি করতে ইমেজ এবং পাঠ্য ডেটা সহ মডেলটিকে অনুরোধ করতে পারেন। PaliGemma মডেলগুলিকে নির্দিষ্ট কাজের জন্য নির্দিষ্ট প্রম্পট সিনট্যাক্স সহ প্রশিক্ষিত করা হয়, যেমন answer , caption এবং detect । PaliGemma প্রম্পট টাস্ক সিনট্যাক্স সম্পর্কে আরও তথ্যের জন্য, PaliGemma প্রম্পট এবং সিস্টেম নির্দেশাবলী দেখুন।

একটি বস্তুর মধ্যে একটি পরীক্ষার চিত্র লোড করতে নিম্নলিখিত কোড ব্যবহার করে একটি প্রজন্মের প্রম্পটে ব্যবহারের জন্য একটি চিত্র প্রস্তুত করুন:

target_size = (224, 224)
image_url = 'https://storage.googleapis.com/keras-cv/models/paligemma/cow_beach_1.png'
cow_image = read_image(image_url, target_size)
matplotlib.pyplot.imshow(cow_image)

একটি নির্দিষ্ট ভাষায় উত্তর দিন

নিম্নলিখিত উদাহরণ কোড দেখায় কিভাবে একটি প্রদত্ত ছবিতে উপস্থিত একটি বস্তু সম্পর্কে তথ্যের জন্য PaliGemma মডেলকে প্রম্পট করতে হয়৷ এই উদাহরণটি answer {lang} সিনট্যাক্স ব্যবহার করে এবং অন্যান্য ভাষায় অতিরিক্ত প্রশ্ন দেখায়:

prompt = 'answer en where is the cow standing?\n'
# prompt = 'svar no hvor står kuen?\n'
# prompt = 'answer fr quelle couleur est le ciel?\n'
# prompt = 'responda pt qual a cor do animal?\n'

output = paligemma.generate(
    inputs={
        "images": cow_image,
        "prompts": prompt,
    }
)
print(output)

detect প্রম্পট ব্যবহার করুন

নিম্নলিখিত উদাহরণ কোড প্রদত্ত ইমেজে একটি বস্তু সনাক্ত করতে detect প্রম্পট সিনট্যাক্স ব্যবহার করে। কোডটি পূর্বে সংজ্ঞায়িত parse_bbox_and_labels() এবং display_boxes() ফাংশন ব্যবহার করে মডেল আউটপুট ব্যাখ্যা করতে এবং জেনারেট করা বাউন্ডিং বাক্সগুলি প্রদর্শন করতে।

prompt = 'detect cow\n'
output = paligemma.generate(
    inputs={
        "images": cow_image,
        "prompts": prompt,
    }
)
boxes, labels = parse_bbox_and_labels(output)
display_boxes(cow_image, boxes, labels, target_size)

segment প্রম্পট ব্যবহার করুন

নিম্নলিখিত উদাহরণ কোড একটি অবজেক্ট দ্বারা দখল করা একটি ছবির এলাকা সনাক্ত করতে segment প্রম্পট সিনট্যাক্স ব্যবহার করে। এটি মডেল আউটপুট ব্যাখ্যা করতে এবং সেগমেন্টেড অবজেক্টের জন্য একটি মাস্ক তৈরি করতে Google big_vision লাইব্রেরি ব্যবহার করে।

শুরু করার আগে, big_vision লাইব্রেরি এবং এর নির্ভরতা ইনস্টল করুন, যেমন এই কোড উদাহরণে দেখানো হয়েছে:

import os
import sys

# TPUs with
if "COLAB_TPU_ADDR" in os.environ:
  raise "It seems you are using Colab with remote TPUs which is not supported."

# Fetch big_vision repository if python doesn't know about it and install
# dependencies needed for this notebook.
if not os.path.exists("big_vision_repo"):
  !git clone --quiet --branch=main --depth=1 \
     https://github.com/google-research/big_vision big_vision_repo

# Append big_vision code to python import path
if "big_vision_repo" not in sys.path:
  sys.path.append("big_vision_repo")


# Install missing dependencies. Assume jax~=0.4.25 with GPU available.
!pip3 install -q "overrides" "ml_collections" "einops~=0.7" "sentencepiece"

এই বিভাজন উদাহরণের জন্য, একটি ভিন্ন চিত্র লোড করুন এবং প্রস্তুত করুন যাতে একটি বিড়াল রয়েছে৷

cat = read_image('https://big-vision-paligemma.hf.space/file=examples/barsik.jpg', target_size)
matplotlib.pyplot.imshow(cat)

PaliGemma থেকে সেগমেন্ট আউটপুট পার্স করতে সাহায্য করার জন্য এখানে একটি ফাংশন রয়েছে

import  big_vision.evaluators.proj.paligemma.transfers.segmentation as segeval
reconstruct_masks = segeval.get_reconstruct_masks('oi')
def parse_segments(detokenized_output: str) -> tuple[np.ndarray, np.ndarray]:
  matches = re.finditer(
      '<loc(?P<y0>\d\d\d\d)><loc(?P<x0>\d\d\d\d)><loc(?P<y1>\d\d\d\d)><loc(?P<x1>\d\d\d\d)>'
      + ''.join(f'<seg(?P<s{i}>\d\d\d)>' for i in range(16)),
      detokenized_output,
  )
  boxes, segs = [], []
  fmt_box = lambda x: float(x) / 1024.0
  for m in matches:
    d = m.groupdict()
    boxes.append([fmt_box(d['y0']), fmt_box(d['x0']), fmt_box(d['y1']), fmt_box(d['x1'])])
    segs.append([int(d[f's{i}']) for i in range(16)])
  return np.array(boxes), np.array(reconstruct_masks(np.array(segs)))

ছবিতে বিড়ালটিকে ভাগ করতে PaliGemma কে জিজ্ঞাসা করুন৷

prompt = 'segment cat\n'
output = paligemma.generate(
    inputs={
        "images": cat,
        "prompts": prompt,
    }
)

PaliGemma থেকে জেনারেট করা মুখোশটি কল্পনা করুন

bboxes, seg_masks = parse_segments(output)
display_segment_output(cat, bboxes, seg_masks, target_size)

ব্যাচ প্রম্পট

আপনি নির্দেশাবলীর একটি ব্যাচ হিসাবে একটি একক প্রম্পটের মধ্যে একাধিক প্রম্পট কমান্ড প্রদান করতে পারেন। নিম্নলিখিত উদাহরণ দেখায় কিভাবে একাধিক নির্দেশাবলী প্রদান করার জন্য আপনার প্রম্পট টেক্সট গঠন করতে হয়।

prompts = [
    'answer en where is the cow standing?\n',
    'answer en what color is the cow?\n',
    'describe en\n',
    'detect cow\n',
    'segment cow\n',
]
images = [cow_image, cow_image, cow_image, cow_image, cow_image]
outputs = paligemma.generate(
    inputs={
        "images": images,
        "prompts": prompts,
    }
)
for output in outputs:
    print(output)